<html manifest="manifest.cache">
<head>
<script src="js/jquery-1.4.2.min.js"></script>
<script src="js/db.js"></script>
<script src="js/oauthsimple.min.js"></script>
<script src="js/OpenDatabase.js"></script>
<script src="js/prototypes.js"></script>
<script>
const Popup = function(){
    if(chrome.experimental.extension.getPopupView()){
        return chrome.experimental.extension.getPopupView();
    }else{
        var v = chrome.extension.getViews(),p;
        for(var i in v){
            if(v[i] && v[i].LT){
                p = v[i];
            }
        }
        return p;
    }
}
const Database = new OpenDatabase('Chrowety');
const m = function(i){return Math.floor(i*60000)};
const s = function(i){return Math.floor(i*1000)};

var isFirstPopupOpen;

var AuthMode = null;

var OAuth = {
    consumer:{
      key: 'eWGZ2e24PmM301P1i0f6bQ',
      secret: '4zwn3jgT4To5Hl6i4fPGkB3mBqkP3Sif5rTVKLPuqg'
    },
    token:{},
    tab:null,

    Sign:function(url, dados, method){
        var sig = {
            consumer_key: OAuth.consumer.key,
            shared_secret: OAuth.consumer.secret
        };
        if(OAuth.token.oauth_token){
            sig.oauth_token = OAuth.token.oauth_token;
            sig.oauth_secret = OAuth.token.oauth_token_secret;
        }
        //console.log(sig);
        return OAuthSimple().sign({
            path: url,
            action: method ? method : 'GET',
            parameters: dados ? dados : {},
            signatures:  sig
        });
    },

    RequestToken:function(out){
        var Tok = new Request(OAuth.Sign(api.request_token).signed_url , 'get', 'text');
        //var Tok = new Request(api.request_token, 'get', 'text');
            Tok.sucesso = function(e){
                var args = e.split("&");
                for(i in args) {
                  args[i] = args[i].split("=");
                  OAuth.token[args[i][0]] = args[i][1];
                }
                try{Popup().init()}
                catch(e){}
            }
            Tok.erro = function(e){
                OAuth.token.erro = true;
                try{Popup().init()}
                catch(e){}
            }
            Tok.init();
    },

    Autorisar:function(){
        var pag = api.autorize+'?oauth_token='+OAuth.token.oauth_token;
        chrome.tabs.create({
            url: pag,
            selected: true
        }, function(tab){
            OAuth.tab = tab.id;
        });
    },

    Access:function(){
        AuthMode = 'OAuth';
        var Acs = new Request(api.access_token, 'get', 'text');
            Acs.dados = {oauth_verifier: OAuth.pin};
            Acs.sucesso = function(e){
                var args = e.split("&");
                for(i in args) {
                  args[i] = args[i].split("=");
                  OAuth.token[args[i][0]] = args[i][1];
                }
                OAuthAutoLogin();
            };
            Acs.initOAuth();
    },

    ParseString:function(str){
        return OAuthSimple()._parseParameterString(str);
    },

    SalvaToken:function(){
        db.salva('token', J2S(OAuth.token));
    },
    LoadToken:function(){
        OAuth.token = S2J(db.pega('token'));
    },
    DeletaToken:function(callback){
        db.deleta('token');
        OAuth.token = {};

        if(callback){
            try{
              eval(callback);
            }catch(e){}
        }
    },

};

function Request(url, met, type, ctype){
        this.url = url;
        this.met = met;
        this.type = type ? type : "json";
        this.dados = {};
        this.sucesso = null;
        this.erro = null;
        this.contentType = ctype ? ctype : "application/x-www-form-urlencoded",

        this.initOAuth = function(){
            if(AuthMode == 'OAuth'){
                this.url = OAuth.Sign(this.url, this.dados, this.met).signed_url;
                this.dados = {};
            }
            this.init();
        }

        this.init = function(){
          $.ajax({
                url: this.url,
                type: this.met,
                data: this.dados,
                dataType: this.type,
                contentType: this.contentType,
                success: this.sucesso,
                error: this.erro,
                timeout: s(6)
             }
          );
        }
}
var tBase = 'https://api.twitter.com/1';
var tBaseOAuth = 'https://api.twitter.com';

var api = {
    access_token:                  tBaseOAuth+ '/oauth/access_token',
    request_token:                 tBaseOAuth+ '/oauth/request_token',
    autorize:                      tBaseOAuth+ '/oauth/authorize',

    login:function(){return        tBase+ '/account/verify_credentials.json'        },
    logout:function(){return       tBase+ '/account/end_session.json'               },
    rate:function(){return         tBase+ '/account/rate_limit_status.json'         },
    home:function(){return         tBase+ '/statuses/home_timeline.json'            },
    friends:function(){return      tBase+ '/statuses/friends_timeline.json'         },
    mentions:function(){return     tBase+ '/statuses/mentions.json'                 },
    messagesSent:function(){return tBase+ '/direct_messages/sent.json'              },
    messages:function(){return     tBase+ '/direct_messages.json'                   },
    favorites:function(){return    tBase+ '/favorites.json'                         },
    update:function(){return       tBase+ '/statuses/update.json'                   },
    updateDM:function(){return     tBase+ '/direct_messages/new.json'               },
    user_show:function(){return    tBase+ '/users/show.json'                        },
    retweet:function(id){return    tBase+ '/statuses/retweet/'+id+'.json'           },
    status:function(id){return     tBase+ '/statuses/show/'+id+'.json'              },
    destroy:function(id){return    tBase+ '/statuses/destroy/'+id+'.json'           },
    destroyDM:function(id){return  tBase+ '/direct_messages/destroy/'+id+'.json'    },
    favorite:function(id){return   tBase+ '/favorites/create/'+id+'.json'           },
    unfavorite:function(id){return tBase+ '/favorites/destroy/'+id+'.json'          },
    follow:function(id){return     tBase+ '/friendships/create/'+id+'.json'         },
    unfollow:function(id){return   tBase+ '/friendships/destroy/'+id+'.json'        },
    block:function(id){return      tBase+ '/blocks/create/'+id+'.json'              },
    unblock:function(id){return    tBase+ '/blocks/destroy/'+id+'.json'             },
    spam:function(){return         tBase+ '/report_spam.json'                       },
    lists:function(user){return    tBase+ '/'+user+'/lists.json'                    },
    listsFollow:function(user){return    tBase+ '/'+user+'/lists/subscriptions.json'},
    list:function(user,lid){return tBase+ '/'+user+'/lists/'+lid+'/statuses.json'   },

    googl:'http://goo.gl/api/url',
    urli: 'http://urli.nl/api.php',
    miudin: 'http://miud.in/api-create.php',
    threely:'http://3.ly/',
    twitpic:'http://twitpic.com/show/',
    twitgoo:'http://twitgoo.com/api/message/info/',
    tweetphoto_view:'http://TweetPhotoAPI.com/api/TPAPI.svc/imagefromurl',
    tweetphoto_post:'http://tweetphotoapi.com/api/tpapi.svc/upload2',
    migre_short:'http://migre.me/api.xml',
    migre_long:'http://migre.me/api_redirect2.xml',
    bitly_short:'http://api.bit.ly/shorten',
    jmp_short:'http://api.j.mp/shorten',
    isgd:'http://is.gd/api.php',
    trim:'http://api.tr.im/v1/trim_simple',
    untrim:'http://untr.im/api/ajax/api',

    audio:'http://vjnrv.net/Labs/Chrowety/Res/alerta.wav'
};
var time = {};

var Logado=false,_iniciou,total=0,new_count=0,api_limit = null,api_checked=false,aid,oid,taid;
var AlertaAudioFile = new Audio();
function SinceDate(TD){
    var a = new Date(TD);
    return a.getDate()+'/'+(a.getMonth()+1)+'/'+a.getFullYear();
}

function ApiDate(TD){
    var a = new Date(TD);
    return a.getHours()+':'+a.getMinutes()+':'+a.getSeconds();
}

function TweetData(TD) {
    var TD = new Date(TD);
        //console.log(TD.toUTCString());
    var AD = new Date();
        //console.log(AD.toUTCString());
        /*
    var Tweet = {
        ano: TD.getUTCFullYear(),
        mes: TD.getUTCMonth(),
        dia: TD.getUTCDay(),
        hor: TD.getUTCHours(),
        min: TD.getUTCMinutes(),
        sec: TD.getUTCSeconds()
    };
    var Atual = {
        ano: AD.getUTCFullYear(),
        mes: AD.getUTCMonth(),
        dia: AD.getUTCDay(),
        hor: AD.getUTCHours(),
        min: AD.getUTCMinutes(),
        sec: AD.getUTCSeconds()
    };

    console.log(Tweet);
    console.log(Atual);
    var offset = TD.getTimezoneOffset() / 60;
    */
    var TD_ = Date.parse(TD); //Date.parse(TD.toUTCString());
    var s;
    //var Calc = (new Date(new Date().toUTCString()).getTime() - TD_) / 1000;
    var Calc = (new Date().getTime() - TD_) / 1000;
    if(Calc < 15) {
            return Traduz('just_now');
    }
    else if(Calc < 60) {
            return Traduz('less_than_a_minute_ago');
    }
    else if(Calc < 60 * 60) {
            var Min = parseInt(Calc / 60);
  		    s = (Min > 1) ? Traduz('minutes_ago', [Min]) : Traduz('a_minute_ago');
            return s;
    }
    else if(Calc < 60 * 60 * 24) {
            var Hor = parseInt(Calc / (60 * 60));
  		    s = (Hor > 1) ? Traduz('hours_ago', [Hor]) : Traduz('a_hour_ago');
            return s;
    }
    else if(Calc < 60 * 60 * 24 * 30) {
            var Day = parseInt(Calc / (60 * 60 * 24));
  		    s = (Day > 1) ? Traduz('days_ago', [Day]) : Traduz('a_day_ago');
            return s;
    }
    else if(Calc < 60 * 60 * 24 * 30 * 12) {
            var Month = parseInt(Calc / (60 * 60 * 24 * 30));
  		    s = (Month > 1) ? Traduz('months_ago', [Month]) : Traduz('a_month_ago');
            return s;
    }
    else {
            return Traduz('years_ago');
    }
}

var Origin_tws = {
    home:{
      total:0,
      last:0,
      new_count:0,
      tweets:[],
      tw:[]
    },
    mentions:{
      total:0,
      last:0,
      new_count:0,
      tweets:[],
      tw:[]
    },
    messages:{
      total:0,
      last:0,
      new_count:0,
      tweets:[],
      tw:[]
    },
    favorites:{
      total:0,
      last:0,
      new_count:0,
      tweets:[],
      tw:[]
    },
    conversations:{
      total:0,
      tweets:[],
    },
    lists:{
      loaded:false,
      total:0,
      full_names:[],
      names:[],
      lists:[],
      ativos:[]
    },
    list:[],
    usuarios:[]
};

var tws = CloneOBJ(Origin_tws);

function Traduz(s, e, pl){
    var re = Utils.Chrome.i18n.get(s,e);

    if(re){
        return re;
    }else{
        return s;
    }
}

function LoadIcon(){
	var ico;
	if(config.icone == 'chrome'){
		ico = 'x19_chrome';
	}else if(config.icone == 'chrome2'){
        ico = 'x19_chrome2';
	}else{
		ico = 'x19';
	}
	var pat = 'icones/'+ico+'.png';
	chrome.browserAction.setIcon({path:pat});
}

function LoadConfig(){
    if(!db.pega('version'))
    {
        db.deleta('config');
        db.salva('version', Chrowety.version());
    }
    else if(db.pega('version') != Chrowety.version())
    {
        try{
          if(db.pega('AuthMode') != "API"){
            db.deleta('z_z');
          }
        }catch(e){console.log(e)}
        //db.deleta('config');
        db.salva('version', Chrowety.version());
    }

    if(db.pega('config') && db.pega('config') != null && typeof S2J(db.pega('config')) == "object")
    {
        console.log('LoadConfig() > Definida');
        config = S2J(db.pega('config'));
        if(!config.base_api){
            config.base_api = DefaultConfig.base_api;
        }
        if(!config.translate_tweets_to){
            config.translate_tweets_to = DefaultConfig.translate_tweets_to;
        }
        if(!config.refresh.list){
            config.refresh.list = 5;
        }
        if(!config.icone){
            config.icone = 'normal';
        }
		if(!config.popup_height){
			config.popup_height = '450px';			
		}
		if(!config.show_username){
			config.show_username = "false";
		}
		if(!config.desktop_notifications){
			config.desktop_notifications = "true";
		}
		if(!config.desktop_notifications_timeout){
			config.desktop_notifications_timeout = 10;
		}
		if(!config.audio_alerta){
			config.audio_alerta = "true";
		}
		if(!config.bitly_key){
			config.bitly_key = "R_9feba944d032e9857730684feb87e1be";
		}
		if(!config.bitly_user){
			config.bitly_user = "chrowety";
		}
		if(!config.phantom_replies){
            config.phantom_replies = "true";
		}
		if(!config.youtube_share){
            config.youtube_share = "true";
		}
        if(!config.individual_alerts){
            config.individual_alerts = {
                home: "true",
                mentions: "true",
                messages: "true",
                list: "true",
                search: "true"
            };
        }
		if(!config.Geo){
            config.Geo = {
                enabled: "false",
                Location: [],
                Address: null
            };
		}
        try{
            db.deleta('profile_view');
        }catch(e){};
        db.salva('config', J2S(config));
    }else
    {
        console.log('LoadConfig() > Padrão');
        config = DefaultConfig;
    }

    tBase = config.base_api;
	LoadIcon();
}

function ReLoadConfig(){

    var _NAME_ = new Array('home', 'mentions', 'messages', 'favorites');
    for(n in  _NAME_){
      try{
        window.clearInterval(time[_NAME_[n]]);
      }catch(e){console.log(e)}
    }
    LoadConfig();
    for(n in  _NAME_){
      try{
        console.log('ReLoadConfig() > '+_NAME_[n]);
        time[_NAME_[n]] = setInterval('Chrowety.'+_NAME_[n]+'.Since()', m(config.refresh[_NAME_[n]]));
      }catch(e){console.log(e)}
    }
}

var config = {};
var DefaultConfig = {
    language: 'en',
    base_api: 'https://api.twitter.com/1',
    translate_tweets_to: 'en',
    url_shortener: 'goo.gl',
    tweet_font_size: '9pt',
    tweet_shadow: "false",
    twitter_question: false,
    link_in_bg: "false",
	icone: 'normal',
	popup_height: '450px',
	show_username: "true",
    desktop_notifications: 'true',
    desktop_notifications_timeout: 10,
    alerts: "false",
    audio_alerta: "true",
    alerts_max:5,
    bitly_key: 'R_9feba944d032e9857730684feb87e1be',
    bitly_user: 'chrowety',
    phantom_replies: "true",
    youtube_share: "true",
    individual_alerts:{
        home: "true",
        mentions: "true",
        messages: "true",
        list: "true",
        search: "true"
    },
    Geo:{
        enabled: "false",
        Location: [],
        Address: null
    },
    start_count:{
      home:10,
      mentions:10,
      messages:20,
      favorites:20
    },
    old_count:{
      home:10,
      mentions:10,
      messages:10,
      favorites:20
    },
    refresh:{
      home:3,
      mentions:5,
      messages:7,
      favorites:60,
      limit_check:3,
      profile:60,
      list:5
    }
};

function J2S(obj){
    return JSON.stringify(obj);
}

function S2J(str){
    return JSON.parse(str);
}

function CloneOBJ(obj){
    return S2J(J2S(obj));
}

function Sortear(ob, campo, reverso){
    var ob2 = ob;
    var SortFunc = function(field, reverse, primer){

       reverse = (reverse) ? -1 : 1;

       return function(a,b){

           a = a[field];
           b = b[field];

           if (typeof(primer) != 'undefined'){
               a = primer(a);
               b = primer(b);
           }

           if (a<b) return reverse * -1;
           if (a>b) return reverse * 1;
           return 0;

       }
    };

    return ob2.sort(SortFunc(campo, reverso, parseInt));
}

function SaveCache(){
    var user     = db.pega('user');
    var _NAME_ = new Array('home', 'mentions', 'messages', 'favorites');
    for(n in  _NAME_){
      try{
        tws[_NAME_[n]].ultimo         = Chrowety[_NAME_[n]].ultimo
        tws[_NAME_[n]].primeiro       = Chrowety[_NAME_[n]].primeiro
        tws[_NAME_[n]].primeiro_lista = Chrowety[_NAME_[n]].primeiro_lista
        tws[_NAME_[n]].mostrando      = Chrowety[_NAME_[n]].mostrando
      }catch(e){console.log(e)}
    }
    var _tws     = J2S(tws);
    console.log(tws)
    db.salva(user+'_TwCache', true);
    db.salva(user+'_tws', _tws);
}

function CalculaApiRequests(){
    var a = config.refresh,li=0;
	for(i in tws.list)
    {
		if(tws.list[i] && tws.list[i]._loaded) li++;
	}
	var list = (60/a.list) * li;
    var calc = (60/a.home) + (60/a.mentions) + (60/a.messages) + (60/a.favorites) + list;
    if(!db.pega('hourly_limit'))
    {
        return {numero: '-', porcento: '-'};
    }
    else
    {
        calc = ((calc) + 4).toFixed();
        perc = ((calc / db.pega('hourly_limit')) * 100).toFixed();
        return {numero: calc, porcento: perc};
    }
}
var RateTrava = null;
function RateLimit(func, _Run){
    console.log('RateLimit()');
    if(RateTrava){
        return false;
    }
    RateTrava = true;
    var Rate = new Request(api.rate(), 'get');
        Rate.sucesso = function(json){
            if(json && json.remaining_hits >=0){
                api_limit = json.remaining_hits;
                db.salva('api_limit', json.remaining_hits);
                db.salva('hourly_limit', json.hourly_limit);
                db.salva('api_reset_time', json.reset_time);
                if(api_limit > 0){
                    api_checked = true;
                    console.log('RateLimit() > OK > '+api_limit+' | '+ ApiDate(db.pega('api_reset_time')));
                    if(func){
                      try{eval(func)}catch(e){}
                    }
                }else{
                    if(_Run){
                        setTimeout('RateLimit(\''+func+'\', true)', s(10));
                    }
                    console.log('RateLimit() > Limit Exceeded');
                    try{
                      Popup().RefreshLimit(new_count);
                    }catch(e){}
                }
            }else{
                Rate.erro();
            }
            RateTrava = null;
        }

        Rate.erro = function(e){
            console.log('RateLimit() > FAIL');
            RateTrava = null;
            setTimeout('RateLimit(\''+func+'\')', s(10));
        }

        Rate.initOAuth();
}

function CheckLimit(r){
    RateLimit(r);
}

function ClearUnreads(tm){
    //console.log('Cleaning Unreads > '+tm);

    if(tws.lists && tws.list && tws.list[tm]){
        tws.list[tm].new_count = 0;
        for(id in tws.list[tm].tweets){
            tws.list[tm].tweets[id].read = true;
        }
    }else{
        tws[tm].new_count = 0;
        for(id in tws[tm].tweets){
            tws[tm].tweets[id].read = true;
        }
    }

    MostraCount();
}

function SalvaProfile(json){
  db.salva('id', json.id);
  db.salva('user', json.screen_name);
  db.salva('nome', json.name);
  db.salva('foto', json.profile_image_url);
  db.salva('info', json.description);
  db.salva('local', json.location);
  db.salva('seguidores', json.followers_count);
  db.salva('seguindo', json.friends_count);
  db.salva('favoritos', json.favourites_count);
  db.salva('profile_loaded', true);
}

function SalvaListas(){
    var listas = tws.list;
    var temp = [],n=0;
    for(var i in listas){
        if(listas[i].ativo){
            temp[n] = i;
            n++;
        }
        else{
            continue
        }
    }
    tws.lists.ativos = temp;
    db.salva( db.pega('user') + '_listas_names' , J2S(tws.lists));
    return temp;
}

function LoadListas(){
    time.list = [];
    if(db.pega((db.pega('user')+'_listas'))){
        db.deleta(db.pega('user')+'_listas');
    }
    var listas_n = S2J(db.pega( (db.pega('user') + '_listas_names') ));
    if(listas_n && typeof(listas_n) == 'object'){
        tws.lists = listas_n;
        //for(var i in tws.lists.ativos)
        var i = tws.lists.ativos.length;
        while(i--)
        {
            _i = tws.lists.ativos[i];
            if(!_i) continue;
            console.log('List: '+_i);
            if(!tws.list[_i]){
                tws.list[_i] = {};
                tws.list[_i].total = 0;
                tws.list[_i].new_count = 0;
                tws.list[_i].tweets = [];
                Utils.Tweet.Cache.Run(_i, true);
                Chrowety.List.Run(_i, 'LT.initLists()');
            }
        }
    }else{
        tws.lists = {
            loaded:false,
            total:0,
            full_names:[],
            names:[],
            lists:[],
            ativos:[]
        }
    }
}

function ContaTweets(tm, list){
    var i=0;
    var id=null,fid=null,fit=null;
    if(list){
        var tw = Sortear(tws[tm][list].tweets, 'id', true);
    }else{
        var tw = Sortear(tws[tm].tweets, 'id', true);
    }
    //for(a in tw)
    var a = tw.length;
    while(a--)
    {
      if(!tw[a]) continue;
      i++;
      id = tw[a].id;
      if(list){
          if(i == 1){tws[tm][list].primeiro_lista = id;fid=id}
          tws[tm][list].ultimo = id;
      }else{
          if(i == 1){Chrowety[tm].primeiro_lista = id;fid=id}
          if(!tw[a].own){Chrowety[tm].ultimo = id}
      }
    }
    if(list){
        tws[tm][list].total = i;
    }else{
        tws[tm].total = i;
    }
    //primeiro = id;
    //console.log('ContaTweet() '+tm+': '+i+' LastID: '+id+' FirstID: '+fid+' First_In: '+Chrowety[tm].primeiro_lista);
}

function MostraCount(){
    var Total = tws.home.new_count + tws.mentions.new_count + tws.messages.new_count;
    if(Total == 0){
        Total = '';
    }

    Utils.Chrome.browserAction.text(Total);

    return Total > 0 ? Total : 0;
}

var fec = {

    GetAttr:function(tid, attr)
    {
        return fec.ByTidAll(tid)[0][attr];
    },

    AttrAll:function(tid, attr, value)
    {
        var _tws = this.ByTidAll(tid);
        for(i in _tws)
        {
            _tws[i][attr] = value;
        }
        return _tws;
    },

    ByTidAll:function(tid, DEL){
        var tms = ['home', 'mentions', 'favorites', 'conversations'],
        r1 = [],
        r2 = [],
        tl = tws.list,
        i = 0;
        for(n in tl)
        {
            r2[i] = n;
            i++;
        }

        tms = tms.concat(r2);

        for(i in tms)
        {
            if(tws[ tms[i] ])
            {
                if(fec.ByTid(tms[i], tid))
                {
                    r1[i] = fec.ByTid(tms[i], tid, DEL);
                }
            }
            else if(tws.list[ tms[i] ])
            {
                if(fec.ByTid('list', tid, null, tms[i]))
                {
                    r1[i] = fec.ByTid('list', tid, DEL, tms[i]);
                }
            }
            else
            {
                continue;
            }
        }
        return this.clearNull(r1);
    },

    ByTid:function(tm, tid, del, list){
        if(list)
        {
            var a = tws.list[list].tweets.reverse();
        }else
        {
            var a = tws[tm].tweets.reverse();
        }

        //for(i in a)
        var i = a.length;
        while(i--)
        {
            if(a[i] && a[i].id == tid){
                if(del){
                    delete a[i];
                }
                return a[i];
                break;
            }else if(a[i] && a[i].retweeted_status && a[i].retweeted_status.id == tid){
                if(del){
                    delete a[i];
                }
                return a[i];
                break;
            }
        }
    },

    clearNull:function(ob, n){
        if(ob && typeof(ob) == 'object'){
            var temp = [], i=0;
            for(i in ob){
                //if(ob[i] != 'undefined' && ob[i] != null){
                if(n == i) break;
                if(ob[i] && ob[i].id){
                    temp[temp.length] = ob[i];
                }else{
                    continue;
                }
                i++;
            }
            return temp;
        }else{
            return false;
        }
    },

    ref:function(i, tm, list){
        var re;
        if(list){
            var ob = tws.list[tm].tweets[i];
            re = Utils.UI.Tweet(ob, tm, true);
        }else{
            var ob = tws[tm].tweets[i];
            re = (tm == 'messages') ? Utils.UI.Message(ob, tm) :  Utils.UI.Tweet(ob, tm);
        }
        return re;
    },

    last:function(tm, n, max, list, notifs){
        var re = (notifs?[]:''),ob;
        if(list){
            ob = tws.list[tm].tweets;
        }else{
            ob = tws[tm].tweets;
        }
        //var i = ob.length;
        for(var i=0;i<n;i++)
        //while(i--)
        {
            if(i>=max)break;
            if(notifs){
                re[i] = Utils.UI.Notifications(Sortear(ob, 'id', true)[i], tm);
            }else{
                re += Utils.UI.Page(Sortear(ob, 'id', true)[i], tm);
            }
        }
        return re;
    },

    lastNotifications:function(tm, n, max, list){
        return this.last(tm, n, max, list, true);
    },

    html:function(tm, cf, count, list){
        var i = 0;
        var re='';
        var ob = [];
        var total = 0;
        if(list){
            var _tws = tws.list[tm];
            if(typeof(_tws) == 'object'){
                ob = Sortear(_tws.tweets, 'id', false);
                total = count ? count : 20;
            }
        }else{
            var _tws = tws[tm];
            if(typeof(_tws.tweets) == 'object'){
                ob = Sortear(_tws.tweets, 'id', false);
                total = count ? count : config.start_count[tm];
            }
        }
        var ia = 0;
        var id = ob.length;
        //for(id in ob){
        while(id--)
        {
          if(!ob[id])
          {
                continue;
          }
          if(cf && cf.max){
            //console.log('fec.html() > max: '+cf.max+ ' e: '+ob[id].id);
            if(i > total)break;
            if(ob[id].id == ia)continue;
            if(ob[id].id < cf.max){
              re = re+fec.ref(id, tm, list);
              ia = ob[id].id;
              if(list){
                tws.list[tm].primeiro_lista = tws.list[tm].primeiro =  ia;
              }else{
                Chrowety[tm].primeiro_lista = Chrowety[tm].primeiro =  ia;
              }
              i++;
            }
          }
          else if(cf && cf.since){
            //console.log('fec.html() > since: '+cf.since+ ' e: '+ob[id].id);
            if(i > total)break;
            if(ob[id].id == ia)continue;
            if(ob[id].id > cf.since){
              re = re+fec.ref(id, tm, list);
              ia = ob[id].id;
              if(list){
                tws.list[tm].primeiro_lista = tws.list[tm].primeiro =  ia;
              }else{
                Chrowety[tm].primeiro_lista = Chrowety[tm].primeiro =  ia;
              }
              i++;
            }
          }else{
            if(i > total)break;
            if(ob[id].id == ia)continue;
            re = re+fec.ref(id, tm, list);
            ia = ob[id].id;
              if(list){
                tws.list[tm].primeiro_lista = tws.list[tm].primeiro =  ia;
              }else{
                Chrowety[tm].primeiro_lista = Chrowety[tm].primeiro =  ia;
              }
            i++;
          }

        }
        if(list){
          tws.list[tm].mostrando += i;
        }else{
          Chrowety[tm].mostrando += i;
        }

        //ContaTweets(tm);
        return re;
    }
}

/* CHROWETY CONTROLLER */
var Chrowety = {

    profile_last_view: null, // nome do usuario sendo visualizado

    version:function(){
          var version = 'NaN';
          var xhr = new XMLHttpRequest();
          xhr.open('GET', chrome.extension.getURL('manifest.json'), false);
          xhr.onreadystatechange = function() {
            if (this.readyState == 4) {
              var manifest = JSON.parse(this.responseText);
              version = manifest.version;
            }
          };
          xhr.send();
          return version;
    },


    Run:function(){
        console.log('Chrowety.Run()');
        var guia = db.pega('AbaAtiva');
        try{
            Popup().init();
        }catch(e){}

        if(Utils.Tweet.Cache.Loaded['home'] > 0)
        {
            Chrowety.home.Since();
        }
        else{
            Chrowety.home.Run('LT.home()');
        }

        if(Utils.Tweet.Cache.Loaded['mentions'] > 0)
        {
            Chrowety.mentions.Since();
        }
        else{
            Chrowety.mentions.Run('LT.CheckLoadeds()');
        }


        if(Utils.Tweet.Cache.Loaded['messages'] > 0)
        {
            Chrowety.messages.Since();
            Chrowety.messages.Run(null, true);
        }
        else{
            Chrowety.messages.Run('LT.CheckLoadeds()');
            Chrowety.messages.Run('LT.CheckLoadeds()', true);
        }

        Chrowety.favorites.Run();

        LoadListas();
        time.profile = window.setInterval('Chrowety.profile()', m(config.refresh.profile));
        time.limit = window.setInterval('CheckLimit()', m(config.refresh.limit_check));
    },

    login:function(lembra, login){
      var Login = new Request(api.login(), 'get');
          Login.sucesso = function(json){
              if(AuthMode == "OAuth"){
                  console.log('Chrowety.login() '+AuthMode);
                  db.salva('logado', true);
                  db.salva('AuthMode', 'OAuth');
                  db.salva('version', Chrowety.version());
                  OAuth.SalvaToken();
                  SalvaProfile(json);
                  CheckLimit('Chrowety.Run()', true);
              }else{
                  console.log('Chrowety.login() '+AuthMode);
                  db.salva('z_z', login);
                  console.log('Logado...');
                  Logado = true;
                  AuthMode = 'API';
                  db.salva('logado', lembra);
                  db.salva('AuthMode', 'API');
                  db.salva('version', Chrowety.version());
                  SalvaProfile(json);
                  CheckLimit('Chrowety.Run()', true);
                  Popup().LoginStatus(Traduz('sucess_login'));
                  Popup().init();
                  console.log('Chrowety.login() > OK');
              }

              Utils.Chrome.browserAction.title('Chrowety ('+db.pega('user')+')');

              try{
                Popup().LoadProfile();
              }catch(e){}

          };
          Login.erro = function(){
              if(AuthMode == "OAuth"){
                    Chrowety.login();
              }else{
                Popup().LoginStatus(Traduz('login_failed', '...'));
                console.log('Chrowety.login() > FAIL');
              }
          };
          Login.initOAuth();
    },

    logout:function(lembra){
      Chrowety.Clean();
      Utils.Chrome.browserAction.text();
      console.log('Chrowety.logout()');
      var bak_conf = db.pega('config');
      db.limpa();
      Utils.Tweet.Database.deleta();
      window.clearInterval(time.limit);
      window.clearInterval(time.home);
      window.clearInterval(time.metions);
      window.clearInterval(time.messages);
      window.clearInterval(time.favorites);
      window.clearInterval(time.profile);
      if(bak_conf != null){
        db.salva('config', bak_conf);
      }
      Logado = false;
      if(AuthMode == "OAuth"){
        OAuth.DeletaToken('OAuth.RequestToken(true)');
      }else{
        jQuery.ajaxSetup({'beforeSend': function(xhr){xhr.setRequestHeader("Authorization", "Basic "+db.pega('z_z'))}});
        var Logout = new Request(api.logout(), 'post');
            Logout.sucesso = function(){
              console.log('Chrowety.logout() > OK');
            };
            Logout.erro = function(){
                  console.log('Chrowety.logout() > FAIL');
            };
            Logout.initOAuth();
      }
      AuthMode = null;
    },

    // Atualiza informações do perfil
    profile:function(){
      console.log('Chrowety.profile()');
      var Profile = new Request(api.login(), 'get');
          Profile.sucesso = function(json){
            console.log('Chrowety.profile() > OK');
            SalvaProfile(json);
          };
          Profile.erro = function(){
            console.log('Chrowety.profile() > FAIL');
          };
          Profile.initOAuth();
    },

    user:function(uname){
        var U = tws.usuarios;
        if(U[uname])
        {
            Popup().ShowUserOK(U[uname]);
            return;
        }

        var User = new Request(api.user_show(), 'get');
            User.dados = {screen_name: uname};
            User.sucesso = function(json){
              //console.log('Chrowety.user() > OK');
              U[uname] = json;
              Popup().ShowUserOK(json);
            };
            User.erro = function(){
              console.log('Chrowety.user() > FAIL');
              Popup().ShowUserERRO();
            };
            User.initOAuth();
    },

    update:function(s, reply_tid, tm, callback, rt){
      var src = 'chrowety';
      var Up = new Request(api.update(), 'post');
          if(config.Geo.enabled === 'true'){
              var _ll = config.Geo.Location;
              Up.dados = reply_tid && !rt ? {lat: _ll[0], long: _ll[1], status: s, in_reply_to_status_id: reply_tid, source: src} : {lat: _ll[0], long: _ll[1], status: s, source: src};
          }else{
              Up.dados = reply_tid && !rt ? {status: s, in_reply_to_status_id: reply_tid, source: src} : {status: s, source: src};
          }
          Up.sucesso = function(w){
            console.log('Chrowety.update() > OK');
            ht = Utils.UI.Tweet(w, tm);
            w.own = true;
            tws.home.total++;
            tws.home.tweets[tws.home.total] = w;
            tws.home.tweets[tws.home.total].read = true;
            Utils.Tweet.DetectSaveMention(w, 'home');
                if(!callback)
                {
                    if(reply_tid)
                    {
                        Popup().ReplyOK(reply_tid, tm);
                        fec.AttrAll(reply_tid, 'replied', true);
                    }else
                    {
                        Popup().UpdateOK(ht, tm);
                    }
                }else
                {
                    callback(true);
                }

          }
          Up.erro = function(){
                console.log('Chrowety.update() > FAIL');
                if(!callback){
                    if(reply_tid){
                        Popup().ReplyFAIL(reply_tid, tm, "error");
                        //fec.ByTid(time, tid, true)
                    }else{
                        Popup().UpdateFAIL(reply_tid, tm, "error");
                    }
                }
                else{
                    callback();
                }
          }
          Up.initOAuth();
    },

    updateDM:function(s, user, tid, tm){
      var _NAME_ = 'messages';
      var Up = new Request(api.updateDM(), 'post');
          Up.dados = {screen_name: user, text: s};
          Up.sucesso = function(w){
            console.log('Message send: '+s);
            ht = Utils.UI.Message(w, tm);
            tws[_NAME_].total++;
            tws[_NAME_].tweets[tws[_NAME_].total] = w;
            tws[_NAME_].tweets[tws[_NAME_].total].read = true;

            Chrowety[_NAME_].ultimo = w.id;
            try{
                Popup().ReplyDMOK(tid, (tm ? tm : _NAME_), ht);
            }
            catch(e){}
            console.log('Chrowety.updateDM() > OK')
          }
          Up.erro = function(e){
                console.log('Chrowety.updateDM() > FAIL');
                var status = e.statusText;
                if(status == "Forbidden"){
                    Popup().ReplyDMFAIL(tid, tm, "forbidden");
                    console.log("You cannot send a direct message to "+user+" because they are not following you.");
                }else{
                    Popup().ReplyDMFAIL(tid, tm, "error");
                }
          }
          Up.initOAuth();
    },


    deleta:function(tid, time, rt){
      var del = new Request(api.destroy(tid), 'post');
          del.sucesso = function(w){
              if(rt)
              {
                  try{
                      Popup().UndoRTOK(tid, time, rt);
                  }catch(e){}
                  fec.ByTidAll(tid, true);
                  fec.AttrAll(rt, 'retweeted_by_me', false);
                  fec.AttrAll(rt, 'retweeted_by_me_status', null);
              }else
              {
                  Utils.Tweet.Deleta(tid);
                  Popup().DeletaOK(tid, time);
              }
              console.log('Chrowety.deleta() > OK');
          }
          del.erro = function(e){
              console.log('Chrowety.deleta() > FAIL');
              if(rt){
                  Popup().UndoRTFAIL(tid, time, rt);
              }else{
                  if(e && e.responseText)
                  {
                      e = S2J(e.responseText).error;
                  }
                  if(e === "No status found with that ID.")
                  {
                      Utils.Tweet.Deleta(tid);
                      Popup().DeletaOK(tid, time);
                  }
                  else
                  {
                      Popup().DeletaFAIL(tid, time);
                  }
              }
          }
          del.initOAuth();
    },

    deletaDM:function(tid, time){
      var del = new Request(api.destroyDM(tid), 'post');
          del.sucesso = function(){
                fec.ByTid(time, tid, true);
                Utils.Tweet.Database.deleta(tid);
                try{
                    Popup().DeletaOK(tid, time);
                }catch(e){}
                console.log('Chrowety.deletaDM() > OK');
          }
          del.erro = function(){
                try{
                    Popup().DeletaFAIL(tid, time);
                }catch(e){}
                console.log('Chrowety.deletaDM() > FAIL');
          }
          del.initOAuth();
    },

    retweet:function(tid, time){
      var rt = new Request(api.retweet(tid), 'post');
          rt.sucesso = function(w){
            console.log('Retweeted: '+tid);
            /*
            w.own = true;
            tws.home.total++;
            tws.home.tweets[tws.home.total] = w;
            tws.home.tweets[tws.home.total].read = true;
            */
            fec.AttrAll(tid, 'retweeted_by_me', true);
            fec.AttrAll(tid, 'retweeted_by_me_status', w.id);
            Popup().RetweetOK(tid, time, w.id);
          }
          rt.erro = function(e){
            var status = 'error';
            try{
                status = e && e.statusText ?  e.statusText : status;
            }catch(e){}
            if(status == "Forbidden"){
                Popup().RetweetFAIL(tid, time, "forbidden");
            }else{
                Popup().RetweetFAIL(tid, time, "error");
            }
            console.log('Chrowety.retweet() > FAIL');
          }
          rt.initOAuth();
    },

    fav_active:false,
    favorite:function(tid, time, list){
      console.log('favorite: '+tid+' - '+time);
      Chrowety.fav_active = true;
      var _fws, _tw;
      var fav = new Request(api.favorite(tid), 'post');
          fav.sucesso = function(){
            console.log('Favoriting tweet: '+tid);
            _tw = fec.AttrAll(tid, 'favorited', true)[0];
            try{
              _fws = tws['favorites'];
              _fws.total++;
              _fws.tweets[_fws.total] = _tw;
            }catch(e){}
            Popup().FavOK(tid, true, time);
            Chrowety.fav_active = false;
          }
          fav.erro = function(){
                console.log('Chrowety.favorite() > FAIL');
                Popup().FavOK(tid, false, time);
          }
          fav.initOAuth();
    },

    unfav_active:false,
    unfavorite:function(tid, time, list){
      Chrowety.unfav_active = true;
      var fav = new Request(api.unfavorite(tid), 'post');
          fav.sucesso = function(){
            console.log('Unfavoriting tweet: '+tid);
            //fec.ByTid(time, tid, null, list).favorited = false;
            fec.AttrAll(tid, 'favorited', false);
            fec.ByTid('favorites', tid, true);
            Popup().FavOK(tid, false, time);
            Chrowety.unfav_active = false;
          }
          fav.erro = function(){
                console.log('Chrowety.unfavorite() > FAIL');
                Popup().FavOK(tid, true, time);
          }
          fav.initOAuth();
    },

    Clean:function(){
        var _NAME_ = new Array('home', 'mentions', 'messages', 'favorites');
        for(n in  _NAME_){
          try{
            console.log('Chrowety.Clean() > '+_NAME_[n]);
            Chrowety[_NAME_[n]]._loaded = false;
            Chrowety[_NAME_[n]].ultimo = null;
            Chrowety[_NAME_[n]].primeiro = null;
            Chrowety[_NAME_[n]].primeiro_lista = null;
            Chrowety[_NAME_[n]].scroll = 0;
            Chrowety[_NAME_[n]].pagina = null;
          }catch(e){console.log(e)}
        }
        db.deleta('AbaAtiva');
        tws = Origin_tws;
    },


    Lists:function(callback){
        var _NAME_ = 'lists';
        var User   = db.pega('user');

        var Sucesso = function(json,s){
               if(typeof tws[_NAME_] != 'object'){
                    tws[_NAME_] = [];
               }
               tws[_NAME_].names = [];
               tws[_NAME_].full_names = [];
               tws[_NAME_].total = 0;
               $.each(json.lists,function(n,w){
                   tws[_NAME_].names[tws[_NAME_].total] = w.slug;
                   tws[_NAME_].full_names[tws[_NAME_].total] = w.full_name;
                   tws[_NAME_].lists[tws[_NAME_].total] = w;
                   if(typeof tws.list != 'object'){
                      tws.list = [];
                   }
                   if(!tws.list[w.slug]){
                       tws.list[w.slug] = {};
                       tws.list[w.slug].total = 0;
                       tws.list[w.slug].tweets = [];
                   }
                   tws[_NAME_].total++;
               });
               time.list = [];
               tws.lists.loaded = true;
               SalvaListas();
               if(callback){
                    try{eval('Popup().'+callback)}catch(e){}
               }else{
                    try{
                         Popup().LT.Lists(tws[_NAME_].names);
                    }catch(e){}
               }
        }
        var Lists = new Request(api[_NAME_](User), 'get');
            Lists.sucesso = Sucesso;
            Lists.initOAuth();

        var ListsFollow = new Request(api['listsFollow'](User), 'get');
            ListsFollow.sucesso = Sucesso;
            //ListsFollow.initOAuth();
    },

    List: {

        Run: function(lid, callback){
            var _NAME_ = 'list';
            var User   = db.pega('user');
            var List = new Request(api[_NAME_](User,lid), 'get');
                List.dados = {per_page: 10, page: 1};
                List.sucesso = function(json,s){
                        if(!tws.list[lid]){
                           tws.list[lid] = {};
                           tws.list[lid].total = 0;
                           tws.list[lid].tweets = [];
                        }
                        var id, _tws = tws.list[lid];
                        $.each(json,function(n,w){
                          taid = w.id;
                          id = w.retweeted_status ? w.retweeted_status.id : w.id;
                          aid = id;
                          _tws.total++;
                          _tws.tweets[_tws.total] = w;
                          _tws.tweets[_tws.total].read = true;
                          if(n == 0){_tws.primeiro_lista = taid}
                        });
                        _tws._loaded = true;
                        _tws.ultimo  = taid;
                        _tws.ativo   = true;
                        _tws.tweets = fec.clearNull(_tws.tweets);
                        tws.lists.ativos[tws.lists.ativos.length] = lid;
                        time[_NAME_][lid] = setInterval('Chrowety.List.Since(\''+lid+'\')', m(config.refresh[_NAME_]));
                        if(callback){
                          try{eval('Popup().'+callback)}catch(e){}
                        }
                        SalvaListas();
                        Utils.Tweet.Cache.Save(lid, true);
                }
                List.erro = function(re){
                    console.log('Chrowety.List.Run('+lid+') > FAIL');
                    window.setTimeout('Chrowety.List.Run(\''+lid+'\', \''+callback+'\')', m(1));
                }
                List.initOAuth();
        },

        Since:function(lid, since){ // Rate Limited
            var _NAME_ = 'list';
            if(!api_limit){return false}
            clearInterval(time[_NAME_][lid]);
            console.log('Chrowety.List.Since('+lid+')');
            ContaTweets(_NAME_, lid);
            var last = since ? since : tws.list[lid].ultimo;
            var novs = 0;
            var User   = db.pega('user');
            var Since = new Request(api[_NAME_](User,lid), 'get');
                Since.dados = {since_id: last};
                Since.sucesso = function(json,s){
                              var id, _tws = tws.list[lid];
                              $.each(json,function(n,w){
                                n++;
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = false;
                                novs = n;
                              });
                              time[_NAME_][lid] = setInterval('Chrowety.List.Since(\''+lid+'\')', m(config.refresh[_NAME_]));
                              tws.list[lid].ultimo = taid;
                              Utils.Tweet.Notify(novs, lid, true);
                              SalvaListas();
                              Utils.Tweet.Cache.Save(lid, true);
                }
                Since.erro = function(){
                    console.log('Chrowety.List.Since('+lid+') > FAIL');
                    window.setTimeout('Chrowety.List.Since(\''+lid+'\', \''+since+'\')', m(config.refresh[_NAME_]));
                }
                Since.initOAuth();
        },

        Max:function(lid, max){ // Rate Limited
            var _NAME_ = 'list';
            console.log('Chrowety.Lists.Max("'+lid+'")');
            if(!api_limit){return false}
            ContaTweets(_NAME_, lid);
            var first = max ? max : tws.list[lid].primeiro;
            var re = '';
            re = fec.html(lid, {max:first}, null, true);
            console.log('fec.html("'+lid+'")');
            if(!re){
              var User   = db.pega('user');
              var Max = new Request(api[_NAME_](User,lid), 'get');
                  Max.dados = {count: 10, max_id: first};
                  Max.sucesso = function(json,s){
                                var id, _tws = tws.list[lid];
                                $.each(json,function(n,w){
                                  if(n == 0){return;}
                                  taid = w.id;
                                  id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                  oid = id;
                                  ht = Utils.UI.Tweet(w, _NAME_, 'read');
                                  re = re+ht;
                                  _tws.total++;
                                  _tws.tweets[_tws.total] = w;
                                  _tws.tweets[_tws.total].read = true;
                                });
                                tws.list[lid].primeiro = taid;
                                try{
                                  Popup().ShowMoreOK(re, _NAME_, lid);
                                  Popup().ShowMoreFAIL(re, _NAME_, lid);
                                }catch(e){}
                                //eval('Popup().'+callback);
                                console.log('Chrowety.List.Max('+lid+') > Pegou do Online');
                }
                Max.erro = function(){
                    console.log('Chrowety.List.Max('+lid+') > FAIL');
                    Popup().ShowMoreFAIL(re, _NAME_, lid);
                }
                Max.initOAuth();
            }else{
                console.log('Chrowety.List.Max('+lid+') > Pegou do Cache');
                Popup().ShowMoreOK(re, _NAME_, lid);
            }
        },
   },

    home: {
        NAME: 'home',
        _loaded:false,
        scroll:0,
        mostrando:0,
        ultimo:null,
        primeiro:null,
        primeiro_lista:null,
        RunTrava: null,
        SinceTrava: null,

        Run:function(callback){ // Rate Limited
            var _NAME_ = 'home';
            if(!api_limit){
              return false;
            }
            if(Chrowety[_NAME_].RunTrava){
              return;
            }
            console.log('Chrowety.'+_NAME_+'.Run()');
            var Run = new Request(api[_NAME_](), 'get');
                Run.dados = {count:config.start_count[_NAME_]};
                Run.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = true;
                                Utils.Tweet.SalvaUsuario(w);
                                if(n == 0){Chrowety[_NAME_].primeiro_lista = taid}
                              });
                              Chrowety[_NAME_]._loaded = true;
                              Chrowety[_NAME_].ultimo = taid;
                              time[_NAME_] = setInterval('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                              if(callback){
                                try{eval('Popup().'+callback)}catch(e){}
                              }
                              Chrowety[_NAME_].RunTrava = null;
                              Utils.Tweet.Cache.Save(_NAME_);
                }
                Run.erro = function(){
                    console.log('Chrowety.'+_NAME_+'.Run() > FAIL');
                    window.setTimeout('Chrowety.'+_NAME_+'.Run(\''+callback+'\')', m(1));
                    Chrowety[_NAME_].RunTrava = null;
                    //Chrowety[_NAME_].Run(callback);
                }
                Run.initOAuth();
                Chrowety[_NAME_].RunTrava = true;
        },
        Since:function(since){ // Rate Limited
            var _NAME_ = 'home';
            if(!api_limit){return false}
            if(Chrowety[_NAME_].SinceTrava){
              return;
            }
            clearInterval(time[_NAME_])
            console.log('Chrowety.'+_NAME_+'.Since()');
            ContaTweets(_NAME_);
            var last = since ? since : Chrowety[_NAME_].ultimo;
            var novs = 0;
            var Since = new Request(api[_NAME_](), 'get');
                Since.dados = (last ? {since_id: last, count: 200} : null);
                Since.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                if(fec.ByTid(_NAME_, w.id)){
                                    return;
                                }
                                n++;
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = false;
                                Utils.Tweet.DetectSaveMention(w, _NAME_);
                                Utils.Tweet.SalvaUsuario(w);
                                novs = n;
                              });
                              Chrowety[_NAME_].SinceTrava = null;
                              time[_NAME_] = setInterval('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                              Chrowety[_NAME_]._loaded = true;
                              Chrowety[_NAME_].ultimo = taid;
                              Utils.Tweet.Notify(novs, _NAME_);
                              Utils.Tweet.Cache.Save(_NAME_);
                }
                Since.erro = function(){
                    Chrowety[_NAME_].SinceTrava = null;
                    console.log('Chrowety.'+_NAME_+'.Since() > FAIL');
                    window.setTimeout('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                }
                Since.initOAuth();
                Chrowety[_NAME_].SinceTrava = true;
        },
        Max:function(max){ // Rate Limited
            var _NAME_ = 'home';
            if(!api_limit){return false}
            console.log('Chrowety.'+_NAME_+'.Max()');
            ContaTweets(_NAME_);
            var first = max ? max : Chrowety[_NAME_].primeiro;
            var re = '';
            re = fec.html(_NAME_, {max:first});
            if(!re){
            var Max = new Request(api[_NAME_](), 'get');
                Max.dados = {count: config.old_count[_NAME_], max_id: first};
                Max.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                if(n == 0){return;}
                                taid = w.id;
                                w.read = true;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                oid = id;
                                ht = Utils.UI.Tweet(w, _NAME_);
                                re = re+ht;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                              });
                              Chrowety[_NAME_].primeiro = taid;
                              Popup().ShowMoreOK(re, _NAME_);
                              console.log('Chrowety.'+_NAME_+'.Max() > Pegou do Online');
                };
                Max.erro = function(){
                    console.log('Chrowety.'+_NAME_+'.Max() > FAIL');
                    Popup().ShowMoreFAIL(re, _NAME_);
                };
                Max.initOAuth();
            }else{
                console.log('Chrowety.'+_NAME_+'.Max() > Pegou do Cache');
                Popup().ShowMoreOK(re, _NAME_);
            }
        },
    },


    mentions: {
        NAME: 'mentions',
        _loaded:false,
        scroll:0,
        mostrando:0,
        ultimo:null,
        primeiro:null,
        primeiro_lista:null,
        RunTrava: null,
        SinceTrava: null,

        Run:function(callback){ // Rate Limited
            var _NAME_ = 'mentions';
            if(!api_limit){return false}
            if(Chrowety[_NAME_].RunTrava){
              return;
            }
            console.log('Chrowety.'+_NAME_+'.Run()');
            var Run = new Request(api[_NAME_](), 'get');
                Run.dados = {count:config.start_count[_NAME_]};
                Run.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = true;
                                Utils.Tweet.SalvaUsuario(w);
                                if(n == 0){Chrowety[_NAME_].primeiro_lista = taid}
                              });
                              Chrowety[_NAME_]._loaded = true;
                              Chrowety[_NAME_].ultimo = taid;
                              time[_NAME_] = setInterval('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                              if(callback){
                                try{eval('Popup().'+callback)}catch(e){}
                              }
                              Chrowety[_NAME_].RunTrava = null;
                              Utils.Tweet.Cache.Save(_NAME_);
                };
                Run.erro = function(){
                    //Chrowety[_NAME_].Run(callback);
                    window.setTimeout('Chrowety.'+_NAME_+'.Run(\''+callback+'\')', m(1));
                    Chrowety[_NAME_].RunTrava = null;
                };
                Run.initOAuth();
                Chrowety[_NAME_].RunTrava = true;
        },
        Since:function(since){ // Rate Limited
            var _NAME_ = 'mentions';
            if(!api_limit){return false}
            if(Chrowety[_NAME_].SinceTrava){
              return;
            }
            clearInterval(time[_NAME_]);
            console.log('Chrowety.'+_NAME_+'.Since()');
            ContaTweets(_NAME_);
            var last = since ? since : Chrowety[_NAME_].ultimo;
            var novs = 0;
            var Since = new Request(api[_NAME_](), 'get');
                Since.dados = (last ? {since_id: last} : null);
                Since.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                if(fec.ByTid(_NAME_, w.id)){
                                    return;
                                }
                                n++;
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = false;
                                Utils.Tweet.DetectSaveMention(w, _NAME_);
                                Utils.Tweet.SalvaUsuario(w);
                                novs = n;
                              });
                              time[_NAME_] = setInterval('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                              Chrowety[_NAME_]._loaded = true;
                              Chrowety[_NAME_].ultimo = taid;
                              Chrowety[_NAME_].SinceTrava = null;
                              Utils.Tweet.Notify(novs, _NAME_);
                              Utils.Tweet.Cache.Save(_NAME_);
                };
                Since.erro = function(){
                    console.log('Chrowety.'+_NAME_+'.Since() > FAIL');
                    window.setTimeout('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                    Chrowety[_NAME_].SinceTrava = null;
                };
                Since.initOAuth();
                Chrowety[_NAME_].SinceTrava = true;
        },
        Max:function(max){ // Rate Limited
            var _NAME_ = 'mentions';
            if(!api_limit){return false}
            console.log('Chrowety.'+_NAME_+'.Max()');
            ContaTweets(_NAME_);
            var first = max ? max : Chrowety[_NAME_].primeiro;
            var re = '';
            re = fec.html(_NAME_, {max:first});
            if(!re){
            var Max = new Request(api[_NAME_](), 'get');
                Max.dados = {count: config.old_count[_NAME_], max_id: first};
                Max.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                if(n == 0){return;}
                                taid = w.id;
                                w.read = true;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                oid = id;
                                ht = Utils.UI.Tweet(w, _NAME_);
                                re = re+ht;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                              });
                              Chrowety[_NAME_].primeiro = taid;
                              Popup().ShowMoreOK(re, _NAME_);
                };
                Max.erro = function(){
                    console.log('Chrowety.'+_NAME_+'.Max() > FAIL');
                    Popup().ShowMoreFAIL(re, _NAME_);
                };
                Max.initOAuth();
            }else{
                console.log('Chrowety.'+_NAME_+'.Max() > Pegou do Cache');
                Popup().ShowMoreOK(re, _NAME_);
            }
        },

    },


    messages: {
        NAME: 'messages',
        _loaded:false,
        scroll:0,
        mostrando:0,
        ultimo:null,
        primeiro:null,
        primeiro_lista:null,
        RunTrava: null,
        RunSentTrava: null,
        SinceTrava: null,

        Run:function(callback, sent){ // Rate Limited
            var _NAME_ = 'messages';
            var _ap;
            if(!api_limit){return false}
            if(sent){
                _ap = 'messagesSent';
                if(Chrowety[_NAME_].RunSentTrava){
                  return;
                }
            }
            else{
                _ap = 'messages';
                if(Chrowety[_NAME_].RunTrava){
                  return;
                }
            }
            console.log('Chrowety.'+_ap+'.Run()');
            var Run = new Request(api[_ap](), 'get');
                Run.dados = {count:config.start_count[_NAME_]};
                Run.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              Utils.Tweet.Database.salva(json, _NAME_);
                              $.each(json,function(n,w){
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = true;
                                if(n == 0){Chrowety[_NAME_].primeiro_lista = taid}
                              });
                              Chrowety[_NAME_]._loaded = true;
                              Chrowety[_NAME_].ultimo = taid;
                              time[_NAME_] = setInterval('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                              if(callback){
                                try{eval('Popup().'+callback)}catch(e){}
                              }
                              if(sent){
                                  Chrowety[_NAME_].RunSentTrava = null;
                              }
                              else{
                                  Chrowety[_NAME_].RunTrava = null;
                              }
                              Utils.Tweet.Cache.Save(_NAME_);
                }

                Run.erro = function(){
                    console.log('Chrowety.'+_ap+'.Run() > FAIL');
                    if(sent){
                        Chrowety[_NAME_].RunSentTrava = null;
                        window.setTimeout('Chrowety.'+_NAME_+'.Run(\''+callback+'\', true)', m(1));
                    }
                    else{
                        Chrowety[_NAME_].RunTrava = null;
                        window.setTimeout('Chrowety.'+_NAME_+'.Run(\''+callback+'\')', m(1));
                    }
                }

                Run.initOAuth();
                if(sent){
                    Chrowety[_NAME_].RunSentTrava = true;
                }
                else{
                    Chrowety[_NAME_].RunTrava = true;
                }
        },
        Since:function(since){// Rate Limited
            var _NAME_ = 'messages';
            if(!api_limit){return false}
            if(Chrowety[_NAME_].SinceTrava){
              return;
            }
            clearInterval(time[_NAME_])
            console.log('Chrowety.'+_NAME_+'.Since()');
            ContaTweets(_NAME_);
            var last = since ? since : Chrowety[_NAME_].ultimo;
            var novs = 0;
            var Since = new Request(api[_NAME_](), 'get');
                Since.dados = (last ? {since_id: last} : null);
                Since.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              Utils.Tweet.Database.salva(json, _NAME_);
                              $.each(json,function(n,w){
                                n++;
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = false;
                                novs = n;
                              });
                              Chrowety[_NAME_].SinceTrava = null;
                              time[_NAME_] = setInterval('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                              Chrowety[_NAME_]._loaded = true;
                              Chrowety[_NAME_].ultimo = taid;
                              Utils.Tweet.Notify(novs, _NAME_);
                              Utils.Tweet.Cache.Save(_NAME_);
                };
                Since.erro = function(){
                    window.setTimeout('Chrowety.'+_NAME_+'.Since()', m(config.refresh[_NAME_]));
                    console.log('Chrowety.'+_NAME_+'.Since() > FAIL');
                    Chrowety[_NAME_].SinceTrava = null;
                };
                Since.initOAuth();
                Chrowety[_NAME_].SinceTrava = true;
        },
        Max:function(max){// Rate Limited
            var _NAME_ = 'messages';
            if(!api_limit){return false}
            console.log('Chrowety.'+_NAME_+'.Max()');
            ContaTweets(_NAME_);
            var first = max ? max : Chrowety[_NAME_].primeiro;
            var re = '';
            re = fec.html(_NAME_, {max:first});
            if(!re){
            var Max = new Request(api[_NAME_](), 'get');
                Max.dados = {count: config.old_count[_NAME_], max_id: first};
                Max.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                if(n == 0){return;}
                                taid = w.id;
                                w.read = true;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                oid = id;
                                ht = Utils.UI.Message(w, _NAME_);
                                re = re+ht;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                              });
                              Chrowety[_NAME_].primeiro = taid;
                              Popup().ShowMoreOK(re, _NAME_);
                };
                Max.erro = function(){
                    console.log('Chrowety.'+_NAME_+'.Max() > FAIL');
                    Popup().ShowMoreFAIL(re, _NAME_);
                };
                Max.initOAuth();
            }else{
                console.log('Chrowety.'+_NAME_+'.Max() > Pegou do Cache');
                Popup().ShowMoreOK(re, _NAME_);
            }
        },

    },

    favorites: {
        NAME: 'favorites',
        _loaded:false,
        scroll:0,
        mostrando:0,
        ultimo:null,
        pagina:1,
        primeiro_lista:null,
        RunTrava: null,
        SinceTrava: null,

        Run:function(callback){// Rate Limited
            var _NAME_ = 'favorites';
            if(!api_limit){return false}
            if(Chrowety[_NAME_].RunTrava){
              return;
            }
            console.log('Chrowety.'+_NAME_+'.Run()');
            tws[_NAME_].total = 0;
            var Run = new Request(api[_NAME_](), 'get');
                Run.dados = {page: 1};
                Run.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              Utils.Tweet.Database.salva(json, _NAME_);
                              $.each(json,function(n,w){
                                taid = w.id;
                                id = w.retweeted_status ? w.retweeted_status.id : w.id;
                                aid = id;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                                _tws.tweets[_tws.total].read = true;
                                Utils.Tweet.SalvaUsuario(w);
                              });
                              Chrowety[_NAME_].pagina = 1;
                              Chrowety[_NAME_]._loaded = true;
                              clearInterval(time[_NAME_]);
                              time[_NAME_] = setInterval('Chrowety.'+_NAME_+'.Run()', m(config.refresh[_NAME_]));
                              if(callback){
                                try{eval('Popup().'+callback)}catch(e){}
                              }
                              Chrowety[_NAME_].RunTrava = null;
                };
                Run.erro = function(){
                    console.log('Chrowety.'+_NAME_+'.Run() > FAIL');
                    clearInterval(time[_NAME_]);
                    //Chrowety[_NAME_].Run(callback);
                    window.setTimeout('Chrowety.'+_NAME_+'.Run(\''+callback+'\')', m(1));
                    Chrowety[_NAME_].RunTrava = null;
                };
                Run.initOAuth();
                Chrowety[_NAME_].RunTrava = true;
        },

        Since:function(){
            return this.Run('LT.Auto()');
        },

        Max:function(pag){// Rate Limited
            var _NAME_ = 'favorites';
            if(!api_limit){return false}
            console.log('Chrowety.'+_NAME_+'.Max()');
            ContaTweets(_NAME_);
            //var pag = pag ? pag : 1;
            Chrowety[_NAME_].pagina += 1;
            var pag = Chrowety[_NAME_].pagina;
            var re = '';
            var Max = new Request(api[_NAME_](), 'get');
                Max.dados = {page: pag};
                Max.sucesso = function(json,s){
                              var id, _tws = tws[_NAME_];
                              $.each(json,function(n,w){
                                w.read = true;
                                ht = Utils.UI.Tweet(w, _NAME_);
                                re = re+ht;
                                _tws.total++;
                                _tws.tweets[_tws.total] = w;
                              });
                              Popup().ShowMoreOK(re, _NAME_);
                };
                Max.erro = function(){
                    console.log('Chrowety.'+_NAME_+'.Max() > FAIL');
                    Popup().ShowMoreFAIL(re, _NAME_);
                };
                Max.initOAuth();
        },

    },
};

function Alerts(n, tm, list){
  Utils.Notify.Build(n,tm,list);

  if(config.audio_alerta == "true"){
      if(AlertaAudioFile.src){
        AlertaAudioFile.play();
      }
      else{
        AlertaAudioFile.src = api.audio;
        AlertaAudioFile.play();
      }
  }

  if(config.alerts == "true"){
      Utils.GetTab(function(Taby){
          if(!Taby.url.match('chrome-extension://') && !Taby.url.match('chrome://')){
              chrome.tabs.executeScript(Taby.id, {
                     file: 'js/jquery-1.4.2.min.js'
                    }, function() {
                        chrome.tabs.insertCSS(Taby.id, {
                               file: 'css/base_pagina.css'
                              }, function() {
                                  chrome.tabs.executeScript(Taby.id, {code:
                                    'var _NAME_ = "'+tm+'"; var _TOTAL_ = "'+n+'";var _MAX_ = "'+config.alerts_max+'"; var _Alerts_ = "'+Traduz('alerts')+'";'
                                  });
                                  chrome.tabs.executeScript(Taby.id, {
                                         file: 'js/script.js'
                                  });
                              }
                        );
                    }
              );
          }
      });
  }
}

var RGX = {
  link: /(^|&lt;|\s)(((https?|ftp):\/\/|mailto:).+?)([\.|\,]\s|[\.|\,]$|\s|&gt;|$)/g,
  nohttp: /(^|&lt;|\s)((www).+?)([\.|\,]\s|[\.|\,]$|\s|&gt;|$)/g,
  //link2: /(^|&lt;|\s)(((https?|ftp):\/\/|mailto:).+?)(\s|&gt;|$)/g,
  twitpic: /((https?):\/\/twitpic.com\/([a-zA-Z_0-9]*|$))/g,
  twigoo: /((https?):\/\/twitgoo.com\/([a-zA-Z_0-9]*|$))/g,
  yfrog: /((https?):\/\/(yfrog.com|yfrog.us)\/([a-zA-Z_0-9]*|$))/g,
  picgd: /((https?):\/\/(tweetphoto.com\/|www.tweetphoto.com\/|pic.gd\/)([a-zA-Z_0-9]*|$))/g,
  youtube: /((https?):\/\/(www.youtube.com\/watch\?v=|youtube.com\/watch\?v=)([*a-zA-Z_0-9-]*|$)([&_a-zA-Z_0-9-=]*|$))/g,
  twitcam: /((https?):\/\/(www.twitcam.com\/|twitcam.com\/)([\)*a-zA-Z_0-9-]*|$))/g,
  twitvid: /((https?):\/\/(www.twitvid.com\/|twitvid.com\/)([\)*a-zA-Z_0-9-]*|$))/g,
  vimeo: /((https?):\/\/(www.vimeo.com\/|vimeo.com\/)([0-9]*|$))/g,
  youtu: /((https?):\/\/(youtu.be\/|www.youtu.be\/)([*a-zA-Z_0-9-]*|$)([?_a-zA-Z_0-9-=]*|$))/g,
  user: /(@|$)([a-zA-Z_0-9]{1,20}|$)/g,
  hash: /(#)(.*?|$)(\s|$)/g
}

var Utils = {

    Regex:{
        Replace: function(txt, web){
            if(!txt){
                return txt;
            }else{
                var hrf = 'nohref';
                var clk = true;
                if(!web)
                {
                    txt = txt.replace(RGX.hash,' #<a class="tag" title="$2" nohref="http://twitter.com/search?q=%23$2" onclick="Link(this, event);">$2</a> ');
                    txt = txt.replace(RGX.user,' $1<a class="usuario" title="$2" nohref="http://twitter.com/$2" onclick="ShowUser(\'$2\')">$2</a>');

                    txt = txt.replace(RGX.twitpic,' <a class="url" nohref="$1" title="$1" onclick="Twitpic(\'$3\');">$1</a>');
                    txt = txt.replace(RGX.twigoo,' <a class="url" nohref="$1" title="$1" onclick="Twitgoo(\'$3\');">$1</a>');
                    txt = txt.replace(RGX.yfrog,' <a class="url" nohref="$1" title="$1" onclick="Yfrog(\'$4\');">$1</a>');
                    txt = txt.replace(RGX.picgd,' <a class="url" nohref="$1" title="$1" onclick="Tweetphoto(\'$1\');">$1</a>');
                    txt = txt.replace(RGX.youtube,' <a class="url" nohref="$1" title="$4" onclick="Youtube(\'$4\');">$1</a>');
                    txt = txt.replace(RGX.twitcam,' <a class="url" nohref="$1" title="$4" onclick="Twitcam(\'$4\');">$1</a>');
                    txt = txt.replace(RGX.twitvid,' <a class="url" nohref="$1" title="$4" onclick="Twitvid(\'$4\');">$1</a>');
                    txt = txt.replace(RGX.vimeo,' <a class="url" nohref="$1" title="$4" onclick="Vimeo(\'$4\');">$1</a>');
                    txt = txt.replace(RGX.youtu,' <a class="url" nohref="$1" title="$4" onclick="Youtube(\'$4\');">$1</a>');

                    txt = txt.replace(RGX.link,' <a class="url" title="$2" href="#" nohref="$2" onclick="Link(this, event);">$2</a>$5 ');
                    txt = txt.replace(RGX.nohttp,' <a class="url" title="$2" href="#" nohref="http://$2" onclick="Link(this, event);">$2</a>$4 ');
                    return txt;
                }
                else
                {
                    txt = txt.replace(RGX.hash,' #<a class="tag" title="$2" href="http://twitter.com/search?q=%23$2" target="_blank" onclick="load()">$2</a> ');
                    txt = txt.replace(RGX.user,' $1<a class="user" title="$2" href="http://twitter.com/$2" target="_blank" onclick="load()">$2</a>');
                    txt = txt.replace(RGX.link,' <a class="url" title="$2" href="$2" target="_blank" onclick="load()">$2</a>$5 ');
                    txt = txt.replace(RGX.nohttp,' <a class="url" title="$2" href="http://$2" target="_blank" onclick="load()">$2</a>$4 ');
                    return txt;
                }

            }
        }
    },

    Error:
    {

    },

    User: // Utils.User
    {
        _FollowAndUnFollow:null,

        FollowAndUnFollow:function(type, uname, callback)
        {
            if(!type || this._FollowAndUnFollow) return;
            var resultado_erro;
            var Up = new Request(api[type](uname), 'post');
            Up.sucesso = function(w)
            {
                if(type === 'follow')
                {
                    resultado_erro = Traduz('you_are_now_following', '@'+uname);
                }
                else
                {
                    resultado_erro = Traduz('you_stopped_following', '@'+uname);
                }

                callback(resultado_erro);
                this._FollowAndUnFollow = null;
            }
            Up.erro = function(e)
            {
                var erro = S2J(e.responseText);
                    erro = erro.error ? erro.error : 'error';

                switch(erro)
                {
                    case 'Could not follow user: '+uname+' is already on your list.':
                        resultado_erro = Traduz('you_are_already_following', '@'+uname);
                        break;
                    case 'You are not friends with the specified user.':
                        resultado_erro = Traduz('you_are_not_following', '@'+uname);
                        break;
                    default:
                        resultado_erro = 'error';
                }

                callback(resultado_erro);
                this._FollowAndUnFollow = null;
            }
            Up.initOAuth();
            this._FollowAndUnFollow = true;
        },

        Follow:function(uname, callback) // Utils.User.Follow()
        {
            this.FollowAndUnFollow('follow', uname, callback);
        },

        UnFollow:function(uname, callback) // Utils.User.UnFollow()
        {
            this.FollowAndUnFollow('unfollow', uname, callback);
        }

    },

    Tweet: // Utils.Tweet
    {
        Deleta:function(tid) // Utils.Tweet.Deleta
        {
            _rid = fec.GetAttr(tid, 'in_reply_to_status_id');
            if(_rid)
            {
                fec.AttrAll(_rid, 'replied', false);
            }
            fec.ByTidAll(tid, true);
            this.Database.deleta(tid);
        },

        SalvaUsuario:function(obj) // Utils.Tweet.SalvaUsuario
        {
            if(!obj instanceof Object) return;

            var _obj = CloneOBJ(obj),
                _tws = tws.usuarios,
                _rtw = (_obj.retweeted_status ? _obj.retweeted_status : false),
                _sts = (_rtw ? _rtw : _obj),
                _usr = _sts.user,
                _user;

            _user = _usr;
            _user.status = _sts;
            delete _user.status.user;
            _tws[_user.screen_name] = _user;
        },

        DetectSaveMention:function(TweetObj, from) // Utils.Tweet.DetectSaveMention
        {
            if(typeof TweetObj != 'object'){
                return false;
            }
            var w = TweetObj,tm,_tws;
            if(from == 'home'){
                tm = 'mentions'
            }else if(from == 'mentions'){
                tm = 'home';
            }else{
                return;
            }

            if(w.text.indexOf('@'+db.pega('user')) != -1){
                _tws = tws[tm];
                _tws.total++;
                _tws.tweets[_tws.total] = w;
                _tws.tweets[_tws.total].read = true;
                return true;
            }else{
                return false;
            }
        },

        Conversation: // Utils.Tweet.Conversation
        {
            action:null,
            html:'',
            timeline:null,

            Retorno:function(html, erro) // Utils.Tweet.Conversation.Retorno()
            {
                console.log(html);
            },

            init:function(tid, timeline, callback) // Utils.Tweet.Conversation.init()
            {
                console.log('Conversation.init()');
                this.action = true;
                this.timeline = timeline;
                this.Retorno = callback;

                this.Get(tid);

            },

            Get:function(tid) // Utils.Tweet.Conversation.Get()
            {
                var attempt = 1,
                max_attempt = 3,
                _this = this;

                if(fec.ByTidAll(tid).length)
                {
                    console.log('Conversation.Get('+tid+') - Cache');
                    _this.Save(fec.ByTidAll(tid)[0]);
                }
                else
                {
                    console.log('Conversation.Get('+tid+') - OK - Attempt '+attempt);
                    var Up = new Request(api.status(tid), 'get');
                    Up.sucesso = function(w)
                    {
                        Utils.Tweet.Conversation.Save(w);
                    }
                    Up.erro = function(e)
                    {
                        if(attempt > max_attempt)
                        {
                            _this.Retorno('', true);
                            _this.End();
                            return;
                        }
                        attempt++;
                        console.log('Conversation.Get('+tid+') - FAIL - Attempt '+attempt);
                        Up.initOAuth();
                    }
                    Up.initOAuth();
                }

            },

            Save:function(tweetObj) // Utils.Tweet.Conversation.Save()
            {
                console.log('Conversation.Save()');
                var w = tweetObj, _tw = tws.conversations;

                _tw.total++;
                _tw.tweets[_tw.total] = w;

                this.html += Utils.UI.Conversation(w);

                if(w.in_reply_to_status_id)
                {
                    console.log('Conversation.Save() > Get...');
                    this.Get(w.in_reply_to_status_id);
                }
                else
                {
                    console.log('Conversation.Save() > Retorno...End...');
                    this.Retorno(this.html);
                    this.End();
                }
            },

            End:function() // Utils.Tweet.Conversation.End()
            {
                console.log('Conversation.End()');
                this.action = false;
                this.timeline = null;
                this.html = '';
            }
        },

        Notify:function(n, time, list) // Utils.Tweet.Notify
        {
            var _tws,alert;

            if(list)
            {
                _tws = tws.list[time];
                alert = config.individual_alerts.list;
            }else
            {
                _tws = tws[time];
                alert = config.individual_alerts[time];
            }

            if(!_tws){
                console.log('Utils.Tweet.Notify() > tws not found');
                return false;
            }

            try{Popup().LT.HideLoad()}catch(e){}

            if(n)
            {
                if(alert === "true")
                {
                    Alerts(n, time, list);
                }
            }

            if(_tws.new_count >= 0)
            {
                _tws.new_count += n;
                var c = _tws.new_count;
                MostraCount();
                try{
                    Popup().RefreshResult(c, time);
                }catch(e){}
                console.log((Traduz(time)).capitalize()+': '+c+(c>1?' '+Traduz('new_tweets'):' '+Traduz('new_tweet')));
            }
        },

        GetGeo:function(tweetObj, tid, time, desktop_alert) // Utils.Tweet.GetGeo(tweetObj, tid, time, desktop_alert)
        {
            if(!tweetObj || !tid || !time) return false;
            var w=tweetObj,re = '',coo;
            if(w.coordinates || w.geo)
            {
                if(w.coordinates.coordinates || w.geo.coordinates)
                {
                    coo = w.coordinates.coordinates ? w.coordinates.coordinates.join(',') : w.geo.coordinates.join(',');
                    if(w.place)
                    {
                        var p = w.place,
                        nome = p.name,
                        polyg = null;
                        if(p.bounding_box)
                        {
                            polyg = J2S(p.bounding_box.coordinates);
                        }
                        if(desktop_alert)
                        {
                            re = '<span class="location cinza p8"></span>';
                        }
                        else
                        {
                            re =
                            '<a title="'+Traduz('show_geo_location')+'" onclick="Map(\''+coo+'\', \''+polyg+'\', '+tid+', \''+time+'\');" class="location cinza p8">'+
                                '<span class="p8">'+nome+'</span>'+
                            '</a>'+
                            '<br />';
                        }

                    }
                    else
                    {
                        if(desktop_alert)
                        {
                            re = '<span class="location cinza p8"></span>';
                        }
                        else
                        {
                            re = '<a title="'+Traduz('show_geo_location')+'" onclick="Map(\''+coo+'\', null, '+tid+', \''+time+'\');" class="location cinza p8"></a>';
                        }
                    }

                }
            }
            else if(w.place)
            {
                var p = w.place;
                var nome = w.place.name;
                var polyg = null;
                if(p.bounding_box)
                {
                    polyg = J2S(p.bounding_box.coordinates);
                }
                if(desktop_alert)
                {
                    re = '<span class="location cinza p8"></span>';
                }
                else
                {
                    re =
                    '<a title="'+Traduz('show_geo_location')+'" onclick="Map(null, \''+polyg+'\', '+tid+', \''+time+'\');" class="location cinza p8">'+
                        '<span class="p8">'+nome+'</span>'+
                    '</a>'+
                    '<br />';
                }
            }

            return re;
        },

        Cache:{
            Loaded:{},

            Run: function(timeline, list, callback)// Utils.Tweet.Cache.Run
            {
                if(!timeline && !list) // Carrega auto
                {
                    this.Load('home');
                    this.Load('mentions');
                    this.Load('messages');
                    this.Load('favorites');

                }
                  else if(!list) // Carrega timeline normal
                  {
                      this.Load(timeline);
                  }
                    else // Carrega listas
                    {
                        this.Load(timeline, true);
                    }

                if(typeof callback == 'function')
                {
                    try{callback()}catch(e){}
                }
                  else
                  {
                      eval(callback)//}catch(e){}
                  }
            },

            Load:function(timeline, list, callback)// Utils.Tweet.Cache.Load
            {
                console.log('Loading Cache: '+timeline);
                var _tws,where;
                if(list){
                    _tws = tws.list[timeline];
                    where = "WHERE timeline = 'list' AND name = '"+timeline+"' ORDER BY id DESC LIMIT 10";
                }else{
                    _tws = tws[timeline];
                    where = "WHERE timeline = '"+timeline+"' ORDER BY id DESC LIMIT 10";
                }

                Utils.Tweet.Database.pega(where, function(rows)
                {
                    var total = rows.length,item;
                    for(var i = 0; i < total ; i++)
                    {
                        item = rows.item(i);
                        _tws.total++;
                        _tws.tweets[_tws.total] = S2J(item.obj);
                        _tws.tweets[_tws.total].read = true;
                    }

                    if(total >= 0)
                    {
                        _tws._loaded = true;
                        if(!list) Chrowety[timeline]._loaded = true;
                    }

                    if(typeof callback == 'function')
                    {
                        try{callback()}catch(e){}
                    }
                      else
                      {
                          eval(callback)//}catch(e){}
                      }

                    if(list)
                    {
                        if(!Utils.Tweet.Cache.Loaded['list'])
                        {
                            Utils.Tweet.Cache.Loaded['list'] = {}
                        }

                        Utils.Tweet.Cache.Loaded['list'][timeline] = total;
                        ContaTweets('list', timeline);
                    }
                      else
                      {
                          Utils.Tweet.Cache.Loaded[timeline] = total;
                          ContaTweets(timeline);
                      }

                    return total;
                });
            },

            Save:function(timeline, list, callback)// Utils.Tweet.Cache.Save
            {
                console.log('Utils.Tweet.Cache.Save('+timeline+', '+list+')');
                var _tws;
                if(list)
                {
                    _tws = tws.list[timeline].tweets;
                    console.log('Tweet Cache List - Deleting');
                    Utils.Tweet.Database.deleta(timeline, 'name', function(t,r){
                        console.log('Tweet Cache List - Saving');
                        Utils.Tweet.Database.salva(_tws, timeline, true);
                    });
                }
                else
                {
                    _tws = tws[timeline].tweets;
                    console.log('Tweet Cache - Deleting');
                    Utils.Tweet.Database.deleta(timeline, 'timeline', function(t,r){
                        console.log('Tweet Cache - Saving');
                        Utils.Tweet.Database.salva(_tws, timeline);
                    });
                }
            }

        },

        Database:{// Utils.Tweet.Database
            tweets: 'tweets',
            users: 'users',

            createTable: function(){// Utils.Tweet.Database.createTable
                //Timelines types: 'home', 'mentions', 'messages', 'favorites', 'list', 'search', 'trends'
                if(!db.pega('tweets_db')){
                    Database.createTable(this.tweets,
                    [
                      'id INTEGER PRIMARY KEY ASC',
                      'obj TEXT',
                      "timeline TEXT",
                      "name TEXT",
                      'created_at DATETIME'
                    ],
                    function(t,r){
                        db.salva('tweets_db', true);
                        //console.log(r);
                    },
                    function(t,r){
                        console.log(r);
                    });
                }
            },
            salva: function(TweetObj, timeline, list){// Utils.Tweet.Database.salva
                this.createTable();
                //console.log('Utils.Tweet.Database.salva');

                if(list)
                {
                    list = timeline;
                    timeline = 'list';
                }
                else
                {
                    list = '';
                }

                for(var i in TweetObj)
                {
                    if(TweetObj[i])
                    {
                        //TweetObj = Sortear(TweetObj, 'id', true);
                        var t = TweetObj[i];
                    }
                    else
                    {
                        var t = TweetObj;
                    }

                    if(!t.id)
                    {
                        continue;
                    }

                    if(i > 10)
                    {
                        break;
                    }

                    Database.insert(this.tweets,
                    {
                        'id': t.id,
                        'obj': J2S(t),
                        'timeline': timeline,
                        'name': list,
                        'created_at': t.created_at
                    },
                    null,
                    function(t,re){
                        //console.log('Campos afetados: '+re.rowsAffected);
                    },
                    function(t,r){
                        //console.log(r);
                    });
                }
            },
            pega: function(where, callback){// Utils.Tweet.Database.pega
                this.createTable();
                Database.select(this.tweets, null, where, function(t,re){
                    if(typeof callback == 'function') callback(re.rows)
                });
            },
            deleta: function(id, type, callback){// Utils.Tweet.Database.deleta
                this.createTable();
                type = type ? type : 'id';
                callback = callback instanceof Function ? callback : function(t,re){}
                Database.remove(this.tweets, (id?'WHERE '+type+' = \''+id+'\'':null), callback);
            }
        }
    },

    Drafts: // Utils.Drafts
    {
        createTable: function(){
            if(!db.pega('drafts')){
                Database.createTable('drafts', ['id INTEGER PRIMARY KEY ASC', 'usuario TEXT', 'texto TEXT', 'data DATETIME'], function(t,r){
                    db.salva('drafts', true);
                });
            }
        },
        salva: function(txt){
            this.createTable();
            Database.insert('drafts', {usuario: db.pega('user'), texto: txt, data: 'NOW()'});
        },
        pega: function(callback){
            this.createTable();
            var html = '';
            Database.select('drafts', null, function(t,re){
                var total = re.rows.length,item;
                for(var i=0; i < total; i++){
                    item = re.rows.item(i);
                    //console.log(item.texto);
                    //html += Utils.UI.Tweet(item);
                    html += '<span>'+item.texto+'</span>';
                }
                if(typeof callback == 'function') callback(html)
                return html;
            });
        },
        deleta: function(id){
            this.createTable();
            Database.remove('drafts', (id?'WHERE id='+id:null), function(t,re){
                //re.rowsAffected
            });
        }
    },

    GetTab: function(callback){
        return Utils.Chrome.tabs.getCurrent(callback);
    },

    Sistema:{
        so: null,
        load:function(){
            var so, ap = navigator.appVersion;
            if(ap.indexOf("Win")!=-1){
                so = "Windows";
            }
            else if(ap.indexOf("Mac")!=-1){
                so = "Mac";
            }
            else if(ap.indexOf("Linux")!=-1){
                so = "Linux";
            }else{
                so = 'Seila';
            }
            Utils.Sistema.so = so;
            return so;
        }
    },

    FormataNumero: function(nStr){
    	nStr += '';
    	x = nStr.split('.');
    	x1 = x[0];
    	x2 = x.length > 1 ? '.' + x[1] : '';
    	var rgx = /(\d+)(\d{3})/;
    	while (rgx.test(x1)) {
    		x1 = x1.replace(rgx, '$1' + ',' + '$2');
    	}
    	return x1 + x2;
    },

    Popup:{
        window:null
    },

    Notify:{
        Show:function(data)
        {
            data = escape(data);
            var Notf = webkitNotifications.createHTMLNotification(chrome.extension.getURL('alerta.html')+'#'+data);
            Notf.show();
        },

        Build:function(n, tm, list)
        {
            if(config.desktop_notifications == 'true')
            {
                var tws = fec.lastNotifications(tm, n, config.alerts_max, list), tw;
                for(i in tws)
                {
                    tw = tws[i];
                    this.Show(tw);
                }
            }
        }
    },

    currentURL:null,

    Translate:{
        loaded:false,

        load:function(resp){
            var JSAPI = document.createElement('script');
                JSAPI.src = 'http://www.google.com/jsapi';
                JSAPI.onload = function(){
                    google.load("language", "1", {
                        callback:function(){
                            Utils.Translate.loaded = true;
                            if(resp) resp();
                        }
                    });
                };
                document.head.appendChild(JSAPI);
        },

        trans:function(txt, tid, tm, list){
            if(!this.loaded){
                this.load(function(){
                    Utils.Translate.trans(txt, tid, tm, list);
                });
                return;
            }

            if(list){
                var tweet = fec.ByTid(tm, tid, null, list);
                if(tweet.translated){
                    Popup().TraduzirOK(tweet.translated, tid, tm);
                    return;
                }
            }else{
                var tweet = fec.ByTid(tm, tid);
                if(tweet.translated){
                    Popup().TraduzirOK(tweet.translated, tid, tm);
                    return;
                }
            }


            var Lingua = config.translate_tweets_to;
            google.language.detect(txt, function(re) {
              if(!re.error && re.language){
                txt = txt.replace('@','0_');
                txt = txt.replace('#','1_');
                google.language.translate(txt, re.language, Lingua, function(re){
                  if(re.translation){
                    var txt = re.translation;
                    txt = txt.replace('0_','@');
                    txt = txt.replace('1_','#');
                    txt = Utils.Regex.Replace(txt);
                    tweet.translated = txt;
                    try{
                      Popup().TraduzirOK(txt, tid, tm);
                    }
                    catch(e){console.log(e)}
                  }else{
                    try{
                      Popup().TraduzirFAIL(re, tid, tm);
                    }
                    catch(e){console.log(e)}
                  }
                });
              }
            });

        }

    },

    Long:{

        Untrim:function(ShortUrl, tid, tm){
            var Un = new Request(api.untrim, 'post', 'html');
                Un.dados = {url: ShortUrl};
                Un.sucesso = function(re){
                    console.log(re);
                    var url = re.getElementsByTagName('a');
                    url = url[url.length-1].innerText;
                    console.log(url);
                    //Popup().ShortLinkOK(tid, tm, url);
                };
                Un.erro = function(e){
                    console.log('Ouve um erro no Untr.im');
                };
                Un.init();
        }
    },

    Short:{

      title:null,
      link:null,

      short:function(LongUrl, tid, tm, cb){
        switch(config.url_shortener){
            case '3.ly':
                LongUrl = encodeURIComponent(LongUrl);
                this.Threely(LongUrl, tid, tm, null, cb);
                break;
            case 'migre.me':
                LongUrl = encodeURIComponent(LongUrl);
                this.MigreMe(LongUrl, tid, tm, cb);
                break;
            case 'goo.gl':
                this.GooGl(LongUrl, tid, tm, cb);
                break;
            case 'bit.ly':
                this.BitLy(LongUrl, tid, tm, null, cb);
                break;
            case 'j.mp':
                this.BitLy(LongUrl, tid, tm, true, cb);
                break;
            case 'is.gd':
                LongUrl = encodeURIComponent(LongUrl);
                this.Threely(LongUrl, tid, tm, 'isgd', cb);
                break;
            case 'tr.im':
                LongUrl = encodeURIComponent(LongUrl);
                this.Threely(LongUrl, tid, tm, 'trim', cb);
                break;
            case 'urli':
                this.Threely(LongUrl, tid, tm, 'urli', cb);
                break;
            case 'miudin':
                this.Threely(LongUrl, tid, tm, 'miudin', cb);
                break;
            default:
                LongUrl = encodeURIComponent(LongUrl);
                this.Threely(LongUrl, tid, tm, null, cb);
        }
      },
	  
      GooGl:function(LongUrl, tid, tm, callback){
        console.log('Shorting URL: '+LongUrl+' With: Goo.gl');
        this.Auth = function(f){function k(){for(var c=0,b=0;b<arguments.length;b++)c=c+arguments[b]&4294967295;return c}function m(c){c=c=String(c>0?c:c+4294967296);var b;b=c;for(var d=0,i=false,j=b.length-1;j>=0;--j){var g=Number(b.charAt(j));if(i){g*=2;d+=Math.floor(g/10)+g%10}else d+=g;i=!i}b=b=d%10;d=0;if(b!=0){d=10-b;if(c.length%2==1){if(d%2==1)d+=9;d/=2}}b=String(d);b+=c;return b}function n(c){for(var b=5381,d=0;d<c.length;d++)b=k(b<<5,b,c.charCodeAt(d));return b}function o(c){for(var b=0,d=0;d<c.length;d++)b=k(c.charCodeAt(d),b<<6,b<<16,-b);return b}f={byteArray_:f,charCodeAt:function(c){return this.byteArray_[c]}};f.length=f.byteArray_.length;var e=n(f.byteArray_);e=e>>2&1073741823;e=e>>4&67108800|e&63;e=e>>4&4193280|e&1023;e=e>>4&245760|e&16383;var l="7";f=o(f.byteArray_);var h=(e>>2&15)<<4|f&15;h|=(e>>6&15)<<12|(f>>8&15)<<8;h|=(e>>10&15)<<20|(f>>16&15)<<16;h|=(e>>14&15)<<28|(f>>24&15)<<24;l+=m(h);return l};
        var shorted;
        var Goo = new Request(api.googl, 'post');
            Goo.dados = {
                user:'toolbar@google.com',
                url: LongUrl,
                auth_token: this.Auth(LongUrl)
            },
            Goo.sucesso = function(re){
                var url = re.short_url;
                Utils.Short.link = url;
                shorted = url;
                console.log(url);
                if(!callback){
                    Popup().ShortLinkOK(tid, tm, url);
                }else{
                    console.log('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                    eval('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                }
            };
            Goo.erro = function(e){
                console.log('Erro no Goo.gl');
                console.log(e.responseText);
                Popup().ShortLinkOK(tid, tm, '');
            };
            Goo.init();
        return shorted;
      },

      BitLy:function(LongUrl, tid, tm, jmp, callback){
        console.log('Shorting URL: '+LongUrl+' With: BitLy');
        var shorted;
        var ap = jmp ? api.jmp_short : api.bitly_short;
        var Bit = new Request(ap, 'get', 'json');
            Bit.dados = {
              longUrl: LongUrl,
              apiKey: config.bitly_key,
              login: config.bitly_user,
              version: '2.0.1'
            };
            Bit.sucesso = function(re){
                var url = re.results[LongUrl].shortUrl;
                url = url ? url : '';
                Utils.Short.link = url;
                shorted = url;
                console.log(url);
                if(!callback){
                    Popup().ShortLinkOK(tid, tm, url);
                }else{
                    console.log('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                    eval('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                }
            };
            Bit.erro = function(e){
                console.log('Erro no BitLy');
                console.log(e.responseText);
                Popup().ShortLinkOK(tid, tm, '');
            };
            Bit.init();
        return shorted;
      },

      MigreMe:function(LongUrl, tid, tm, callback){
        console.log('Shorting URL: '+LongUrl+' With: Migre.me');
        var shorted;
        var Mi = new Request(api.migre_short, 'get', 'xml');
            Mi.dados = {url: LongUrl};
            Mi.sucesso = function(re){
                var url = $('item > migre', $(re)).text();
                Utils.Short.link = url;
                shorted = url;
                console.log(url);
                if(!callback){
                    Popup().ShortLinkOK(tid, tm, url);
                }else{
                    console.log('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                    eval('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                }
            };
            Mi.erro = function(e){
                console.log('Erro no Migre.me');
                console.log(e.responseText);
                Popup().ShortLinkOK(tid, tm, '');
            };
            Mi.init();
        return shorted;
      },

      Threely:function(LongUrl, tid, tm, other, callback){
        console.log('Shorting URL: '+LongUrl+' With: 3.ly/is.gd');
        var shorted;
        var ap,d;
        switch(other){
            case 'isgd':
                console.log('Threely > is.gd');
                ap = api.isgd;
                d  = {longurl: LongUrl};
                break;
            case 'trim':
                console.log('Threely > tr.im');
                ap = api.trim;
                d  = {url: LongUrl};
                break;
            case 'urli':
               console.log('Threely > URLi');
               ap  = api.urli;
               d   = {format: 'simple', action: 'shorturl', url: LongUrl};
               break;
            case 'miudin':
               console.log('Threely > Miud.in');
               ap  = api.miudin;
               //LongUrl = unescape(LongUrl);
               d   = {url: LongUrl};
               break;
            default:
                console.log('Threely > 3.ly');
                ap = api.threely;
                d  = {api: 'em5893833', u: LongUrl};
        }
        var Ly = new Request(ap, 'get', 'text');
            Ly.dados = d;
            Ly.sucesso = function(url){
                Utils.Short.link = url;
                shorted = url;
                console.log(url);
                if(!callback){
                    Popup().ShortLinkOK(tid, tm, url);
                }else{
                    console.log('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                    eval('Popup().'+callback+'(\''+tid+'\', \''+tm+'\', \''+url+'\')');
                }
            };
            Ly.erro = function(e){
                console.log('Erro no 3.ly/is.gd');
                console.log(e.responseText);
                Popup().ShortLinkOK(tid, tm, '');
            };
            Ly.init();
      },

    },

    Yfrog:{
        vendo:null,
        thumb:function(id){
            Utils.Yfrog.vendo = id;
            return 'http://yfrog.com/'+id+'.th.jpg';
        }
    },

    Twitpic:{
        vendo:null,
        thumb:function(id){
            Utils.Twitpic.vendo = id;
            var size = 'thumb';
            return api.twitpic+size+'/'+id;
        }
    },

    Twitgoo:{
        vendo:null,
        thumb:function(id){
            var pic = new Request(api.twitgoo+id, 'get', 'xml');
                pic.sucesso = function(e){
                    Utils.Twitgoo.vendo = id;
                    var url = $('rsp > thumburl', $(e)).text();
                    try{
                      Popup().Twitgoo(id, url);
                    }catch(e){}
                }
                pic.erro = function(e){
                    console.log(e);
                }
                pic.init();
        }
    },

    Tweetphoto:{

        thumb:function(url){
            var size = 'medium';
            return api.tweetphoto_view+'?size='+size+'&url='+url;
        }
    }

};

chrome.extension.onRequest.addListener(function(request, sender, sendResponse){
    if(request.novos_tweets)
    {
      sendResponse({
        'tweets': fec.last(request.tm, request.total, request.max)
      });
    }

    if(request.autorisar)
    {
      OAuth.pin = request.pin;
      chrome.tabs.remove(OAuth.tab);
      OAuth.Access();
    }

    if(request.traduz)
    {
      var re;
        if(typeof(request.texto) == 'object'){
          re = [];
          for(i in request.texto){
              re[i] = Traduz(request.texto[i]);
          }
        }else{
          re = Traduz(request.texto);
        }
        sendResponse({
          'traduzido': re,
          'usuario': db.pega('user'),
          'logado': db.pega('logado')
        });
    }

    if(request.GetConfig)
    {
        sendResponse({
            'config': config
        });
    }

    if(request.shareVideo)
    {
      console.log('Sharing Video...');
      var titulo = request.videoTitle;
      var id     = request.videoID;
      var URL    = ': http://youtu.be/'+id;
      var txt;

      if(140 < titulo.length +URL.length){
          var tirar = 140 -URL.length -3; // 140 -url -3 (dots)
          txt = [];
          for (var i = 0; i < tirar; i++){
              txt[i] = titulo.charAt(i);
          }
          txt[i] = '...';
          txt = txt.join('') +URL;
      }
      else{
          txt = titulo +URL;
      }

      Chrowety.update(txt, null, 'home', function(OK){
          sendResponse({
            'enviou': OK
          });
      });
    }

});

function Logout()
{
    Chrowety.logout();
}

function OAuthAutoLogin()
{
    console.log('OAuthAutoLogin()');
    Logado = true;
    AuthMode = 'OAuth';
    //Chrowety.login(true);
    //Utils.Tweet.Cache.Run();
    Utils.Tweet.Cache.Run(null, null, 'Chrowety.login(true)');
}

function AutoLogin()
{
    console.log('AutoLogin()');
    Logado = true;
    AuthMode = 'API';
    jQuery.ajaxSetup({'beforeSend': function(xhr){xhr.setRequestHeader("Authorization", "Basic "+db.pega('z_z'))}});
    //CheckLimit('Chrowety.Run()', true);
    Utils.Tweet.Cache.Run(null, null, 'CheckLimit(\'Chrowety.Run()\')');
}

function Login(user,senha,lembra)
{
    console.log('Login()');
    var login = btoa(user+':'+senha);
    jQuery.ajaxSetup({'beforeSend': function(xhr){xhr.setRequestHeader("Authorization", "Basic "+login)}});
    Chrowety.login(lembra, login);
}

function BrowserAction()
{
    Utils.Chrome.browserAction.color([119, 190, 190, 190]);
}

function init()
{
    BrowserAction();
    LoadConfig();
    Utils.Sistema.load();

    if(db.pega('logado'))
    {
        if(db.pega('AuthMode') == 'OAuth')
        {
            OAuth.LoadToken();
            OAuthAutoLogin();
        }
        else
        {
            AutoLogin();
        }
    }
    else
    {
        OAuth.RequestToken();
    }
}

$(document).ready(init);
</script>
<script src="js/Utils.UI.js"></script>
<script src="js/Utils.Chrome.js"></script>
</head>
</html>